package de.rayman2200.converter;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Image;
import java.awt.MediaTracker;
import java.awt.Toolkit;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.Transferable;
import java.awt.dnd.DropTargetDragEvent;
import java.awt.dnd.DropTargetDropEvent;
import java.awt.dnd.DropTargetEvent;
import java.awt.dnd.DropTargetListener;
import java.io.File;
import java.net.URL;

import javax.swing.DefaultComboBoxModel;
import javax.swing.ImageIcon;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;

import de.rayman2200.converter.components.JDropableComponent;
import de.rayman2200.converter.plugin.ClipboardConfiguration;
import de.rayman2200.converter.plugin.ClipboardConverterPlugin;
import de.rayman2200.converter.plugin.ConverterPlugin;
import de.rayman2200.converter.plugin.FileConfiguration;
import de.rayman2200.converter.plugin.FileConverterPlugin;
import de.rayman2200.converter.plugin.ToHex;


public class Converter extends JFrame implements DropTargetListener, FileConfiguration,
  ClipboardConfiguration
{

  private static final long serialVersionUID = 907314920971184488L;

  // Default init
  private Position position = Position.LOWER_RIGHT;

  private final JLabel labelTop = new JLabel(" ");

  private final JLabel labelBottom = new JLabel(" ");

  private DefaultComboBoxModel<ConverterPlugin> model = new DefaultComboBoxModel<ConverterPlugin>();

  private JComboBox<ConverterPlugin> plugins = new JComboBox<ConverterPlugin>(model);


  enum Position
  {
    UPPER_LEFT, UPPER, UPPER_RIGHT, RIGHT, LOWER_RIGHT, LOWER, LOWER_LEFT, LEFT
  }


  public Converter()
  {
    init();
  }

  private void init()
  {
    setAlwaysOnTop(true);
    setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
    setLayout(new BorderLayout());
    setTitle("Converter");
    labelBottom.setBackground(Color.WHITE);
    labelTop.setBackground(Color.WHITE);

    Toolkit toolkit = getToolkit();
    Dimension screenSize = toolkit.getScreenSize();

    try
    {
      URL resource = getClass().getResource("/resources/drop-it.png");
//      Image image = toolkit.getImage(resource);
      ImageIcon image = new ImageIcon(resource);
//      MediaTracker mediaTracker = new MediaTracker(this);
//      mediaTracker.addImage(image, 0);
//      mediaTracker.waitForAll();
      add(plugins, BorderLayout.NORTH);
      add(new JDropableComponent(image, this), BorderLayout.CENTER);
      // add(labelBottom, BorderLayout.SOUTH);
      pack();


      alignWindow(getSize(), screenSize, position);
    }
    catch (Exception e)
    {
      e.printStackTrace();
      System.exit(1);
    }
  }

  public void registerPlugin(ConverterPlugin plugin)
  {
    if (plugin instanceof FileConverterPlugin)
    {
      ((FileConverterPlugin)plugin).setFileConfiguration(this);
    }
    if (plugin instanceof ClipboardConverterPlugin)
    {
      ((ClipboardConverterPlugin)plugin).setClipboardConfiguration(this);
    }
    model.addElement(plugin);
  }

  private void alignWindow(Dimension frameSize, Dimension screenSize, Position position)
  {
    int width = screenSize.width;
    int height = screenSize.height;

    int x = 0;
    int y = 0;

    switch (position)
    {
      case UPPER_LEFT:
        break;
      case UPPER:
        x = width / 2 - frameSize.width / 2;
        break;
      case UPPER_RIGHT:
        x = width - frameSize.width;
        break;
      case RIGHT:
        x = width - frameSize.width;
        y = height / 2 - frameSize.height / 2;
        break;
      case LOWER_RIGHT:
        x = width - frameSize.width;
        y = height - frameSize.height;
        break;
      case LOWER:
        x = width / 2 - frameSize.width / 2;
        y = height - frameSize.height;
        break;
      case LOWER_LEFT:
        y = height - frameSize.height;
        break;
      case LEFT:
        y = height / 2 - frameSize.height / 2;
        break;
    }
    setBounds(x, y, frameSize.width, frameSize.height);
  }

  @Override
  public void dragEnter(DropTargetDragEvent dtde)
  {}

  @Override
  public void dragExit(DropTargetEvent dte)
  {}

  @Override
  public void dragOver(DropTargetDragEvent dtde)
  {}

  @SuppressWarnings("unchecked")
  @Override
  public void drop(DropTargetDropEvent dtde)
  {
    try
    {
      Transferable tr = dtde.getTransferable();
      DataFlavor[] flavors = tr.getTransferDataFlavors();
      dtde.acceptDrop(dtde.getDropAction());
      ConverterPlugin plugin = (ConverterPlugin)model.getSelectedItem();
      for ( DataFlavor dataFlavor : flavors )
      {
        Object obj = tr.getTransferData(dataFlavor);
        if (!plugin.canHandle(dataFlavor))
        {
          dtde.rejectDrop();
          return;
        }

        boolean success = plugin.performConvert(obj, dataFlavor);
        if (success)
        {
          dtde.dropComplete(true);
        }
        else
        {
          dtde.rejectDrop();
        }
      }
    }
    catch (Exception e)
    {}
  }

  @Override
  public void dropActionChanged(DropTargetDragEvent dtde)
  {}

  public static void main(String[] args)
  {
    Converter converter = new Converter();
    converter.registerPlugin(new ToHex());
    converter.setVisible(true);
  }

  @Override
  public File createOutputFile()
  {
    return new File("output.hex");
  }

  @Override
  public Clipboard getClipBoard()
  {
    return Toolkit.getDefaultToolkit().getSystemClipboard();
  }

  @Override
  public File getOutputDir()
  {
    return new File("");
  }

  // @Override
  // public OutputType getOutputType()
  // {
  // return OutputType.FILE;
  // }

  @Override
  public File getTempDir()
  {
    return new File("/tmp");
  }
}
